﻿using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Threading.Tasks;
using System.Xml.Linq;

namespace MemorySiteServer.ViewModels.RoleViewModels
{
    public class AllPermissionResponse
    {
        /// <summary>
        /// 权限名称
        /// </summary>
        public string Name { get; set; }
        /// <summary>
        /// 权限所属Controller
        /// </summary>
        public string Controller { get; set; }
        /// <summary>
        /// 权限Action
        /// </summary>
        public string Action { get; set; }

        public async static Task<List<AllPermissionResponse>> GetAllPermissionsAsync()
        {
            List<AllPermissionResponse> allPermisstionResponses = new List<AllPermissionResponse>();
            await Task.Run(() =>
            {
                var xmlFile = $"{Assembly.GetExecutingAssembly().GetName().Name}.xml";
                var xmlPath = Path.Combine(AppContext.BaseDirectory, xmlFile);
                XElement xElement = XElement.Load(xmlPath);
                var members = xElement.Element("members").Elements().Where(x => x.Attribute("name").Value.Contains(".Controllers.")).ToList();
                var typeController = typeof(ControllerBase);
                var typeRoute = typeof(RouteAttribute);
                var typeAuthorize = typeof(AuthorizeAttribute);
                //枚举所有Action
                var controllers = typeof(Startup).Assembly.GetTypes().AsEnumerable()
                    .Where(type => typeController.IsAssignableFrom(type)).ToList();
                controllers.ForEach(controller =>
                {
                    var methods = controller.GetMethods().Where(method => method.CustomAttributes.Any(attribute => typeRoute.IsAssignableFrom(attribute.AttributeType))
                        && method.CustomAttributes.Any(attribute => typeAuthorize.IsAssignableFrom(attribute.AttributeType) &&
                        attribute.NamedArguments.Any(namedArgument => namedArgument.MemberName == "Policy" && namedArgument.TypedValue.Value.ToString() == "site"))).ToList();
                    methods.ForEach(method =>
                        {
                            var member = members.FirstOrDefault(x => x.Attribute("name").Value.Contains($".Controllers.{controller.Name}.{method.Name}"));
                            allPermisstionResponses.Add(new AllPermissionResponse()
                            {
                                Controller = controller.Name.ToUpperInvariant().Remove(controller.Name.Length - 10),
                                //Action = method.CustomAttributes.FirstOrDefault(attribute => typeRoute.IsAssignableFrom(attribute.AttributeType)).ConstructorArguments[0].Value.ToString(),
                                Action = method.Name.ToUpperInvariant(),
                                Name = member.Element("summary").Value.Trim(),
                            });
                            members.Remove(member);
                        }
                    );
                });
            });
            //获取Action的名称
            return allPermisstionResponses;
        }
    }
}
